package com.tyqx.hashchainbiz.service.impl;

import com.mongodb.client.gridfs.GridFSBucket;
import com.tyqx.hashchainbean.module.HashIndex;
import com.tyqx.hashchainbean.module.NoHashValueJson;
import com.tyqx.hashchainbiz.service.NoHashValueJsonService;
import com.tyqx.hashchaindao.mapper.NoHashValueJsonMapper;
import org.bson.types.ObjectId;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;


@Service("noHashValueJsonService")
public class NoHashValueJsonServiceImpl implements NoHashValueJsonService  {

    @Resource
    private NoHashValueJsonMapper noHashValueJsonMapper;

    @Override
    public Integer insert(NoHashValueJson noHashValueJson) {
        return noHashValueJsonMapper.insert(noHashValueJson);
    }

    @Override
    public List<NoHashValueJson> select() {
        return noHashValueJsonMapper.select();
    }

    @Override
    public int deleteByHashValue(String hashValue) {
        return noHashValueJsonMapper.deleteByHashValue(hashValue);
    }

    @Override
    public int deleteByRootHashValue(String rootHashValue) {
        return noHashValueJsonMapper.deleteByRootHashValue(rootHashValue);
    }


    @Override
    public int updateCountByTableNameAndTableId(String hashTableName, Integer hashTableId, String hashValue) {
        return noHashValueJsonMapper.updateCountByTableNameAndTableId(hashTableName, hashTableId, hashValue);
    }

    @Override
    public int updateStatus(Integer status, HashIndex hashIndex) {
        return noHashValueJsonMapper.updateStatus(status,hashIndex);
    }

    @Override
    public NoHashValueJson selectHashIndexByHashValue(String hashValue) {
        return noHashValueJsonMapper.selectHashIndexByHashValue(hashValue);
    }

    @Override
    public List<String> selectUserName(Integer status) {
        return noHashValueJsonMapper.selectUserName(status);
    }

    @Override
    public List<NoHashValueJson> selectByStatus(Integer status) {
        return noHashValueJsonMapper.selectByStatus(status);
    }


    @Override
    public Integer selectCount(String userName) {
        return noHashValueJsonMapper.selectCount(userName);
    }

    @Override
    public List<NoHashValueJson> selectBatchGroupByUserName(String userName, Integer pageSize) {
        return noHashValueJsonMapper.selectBatchGroupByUserName(userName, pageSize);
    }

    @Override
    public Integer updateBatchStatus(Integer status, HashIndex hashIndex, List<Long> idList) {
        return noHashValueJsonMapper.updateBatchStatus(status, hashIndex, idList);
    }

    @Override
    public NoHashValueJson selectHashIndexById(Long id) {
        return noHashValueJsonMapper.selectHashIndexById(id);
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public void insertNoHashValueJsonAndMongoDB(ObjectId objectId, NoHashValueJson noHashValueJson, GridFSBucket gridFSFilesBucket) throws Exception{
        Integer flag = noHashValueJsonMapper.insert(noHashValueJson);

        if (flag == 0) {
            throw new Exception("insert error");
        }

        gridFSFilesBucket.rename(objectId, "mongodb-jzt-attachment-businesss-1");
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Integer insertNoHashValueJsonBatch(List<NoHashValueJson> noHashValueJsonList) throws Exception {
        Integer flag = noHashValueJsonMapper.insertBatch(noHashValueJsonList);
        if (flag == 0) {
            throw new Exception("insert error");
        }
        return  flag;
    }

    @Override
    public void insertMongoDBBatch(List<ObjectId> objectIds, GridFSBucket gridFSFilesBucket,String fileName) throws Exception {
        List<ObjectId> failedObjectIds = new ArrayList<>();
        List<ObjectId> failedObjectIds1 = new ArrayList<>();
        for(int i=0;i<objectIds.size();i++){
            ObjectId objectId=objectIds.get(i);
            try {
                gridFSFilesBucket.rename(objectId, fileName);
            }catch (Exception e){
                e.printStackTrace();
                failedObjectIds.add(objectId);
            }
        }
//        first retry
        if (failedObjectIds.size() > 0){
            Thread.sleep(5);
            for(int i=0;i<failedObjectIds.size();i++){
                ObjectId objectId=failedObjectIds.get(i);
                try {
                    gridFSFilesBucket.rename(objectId, fileName);
                }catch (Exception e){
                    e.printStackTrace();
                    failedObjectIds1.add(objectId);
                }
            }
        }
//        second retry
        if (failedObjectIds1.size() > 0){
            Thread.sleep(10);
            for(int i=0;i<failedObjectIds1.size();i++){
                ObjectId objectId=failedObjectIds1.get(i);
                gridFSFilesBucket.rename(objectId, fileName);
            }
        }
    }

    @Override
    public List<NoHashValueJson> selectByStatusBatch(Integer status, Integer batchSize) {
        return noHashValueJsonMapper.selectByStatusBatch(status, batchSize);
    }

    @Override
    public Integer deleteBatch(List<String> hashValueList) {
        return noHashValueJsonMapper.deleteBatchByHashValue(hashValueList);
    }

}
